public class Apagos {
	static final int nb = 16;
	static final int[] MAX = new int[] {nb, 5, 1, 9, 7};
	
	static final Joueur[] n = new Joueur[2];
	
	static {
		n[0] = new JoueurAleatoire();
		n[1] = new JoueurMinimax(new HToolsU3());
	}
	
	// ******************************************************************************************
	public static void main(String[] args) {
		int i = 0;
		int cpt = 0;
		while (i != 1000) {
			cpt += unePartie();
			i++;
		}
		System.out.println("Le nombre de parties gagnées par le joueur noir vaut :" + cpt);
	}
	
	public static int unePartie() {
		int i = 0;
		
		int[] t = new int[] {nb, 0, 0, 0, 0, nb, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4};
		
		while (nbrSucc(t) != 0) {
			// print(t, i);
			
			int[] u = new int[16];
			copy(t, u);
			int joueur = t[10];
			int[] m = n[joueur].tour(u);
			
			if (isLegal(t, m[0], m[1])) {
				t[joueur * 5 + t[11 + m[0]]]--;
				t[joueur * 5 + t[11 + m[1]]]++;
				t[10] = (t[10] + 1) % 2;
				
				if (m[0] == 0 && m[1] != 1) {
					int tmp = t[11 + m[1]];
					t[11 + m[1]] = t[10 + m[1]];
					t[10 + m[1]] = tmp;
				}
			} else {
				System.out.println("Mouvement illégal");
				System.exit(-1);
			}
			i++;
		}
		// print(t, i);
		
		if (dead(t)) {
			System.out.println("Le Joueur 0 a gagné.");
			return 0;
		} else {
			System.out.println("Le Joueur 1 a gagné.");
			return 1;
		}
	}
	
	public static void print(int[] t, int i) {
		System.out.println("*****************************************************");
		System.out.printf("T: %4d\n", i);
		System.out.printf("J: %4d\n", t[10]);
		System.out.printf("B: %4d, %4d, %4d, %4d, %4d\n", t[t[11]], t[t[12]], t[t[13]], t[t[14]], t[t[15]]);
		System.out.printf("N: %4d, %4d, %4d, %4d, %4d\n", t[5 + t[11]], t[5 + t[12]], t[5 + t[13]], t[5 + t[14]],
				t[5 + t[15]]);
		System.out.printf("P: %4d, %4d, %4d, %4d, %4d\n", t[11], t[12], t[13], t[14], t[15]);
	}
	
	static int[][] succ(int[] t) {
		int[][] r = new int[nbrSucc(t)][18];
		int k = 0;
		
		int i = 0;
		while (i != 5) {
			int j = i + 1;
			while (j != 5) {
				if (t[t[10] * 5 + t[11 + i]] > 0 && t[5 + t[11 + j]] + t[t[11 + j]] < MAX[t[11 + j]]) {
					copy(t, r[k]);
					r[k][t[10] * 5 + t[11 + i]]--;
					r[k][t[10] * 5 + t[11 + j]]++;
					r[k][10] = (r[k][10] + 1) % 2;
					r[k][16] = i;
					r[k][17] = j;
					
					if (i == 0 && j != 1) {
						int tmp = r[k][11 + j];
						r[k][11 + j] = r[k][10 + j];
						r[k][10 + j] = tmp;
					}
					k++;
				}
				j++;
			}
			i++;
		}
		
		return r;
	}
	
	static int nbrSucc(int[] t) {
		int r = 0;
		
		int i = 0;
		while (i != 5) {
			int j = i + 1;
			while (j != 5) {
				if (t[t[10] * 5 + t[11 + i]] > 0 && t[5 + t[11 + j]] + t[t[11 + j]] < MAX[t[11 + j]])
					r++;
				j++;
			}
			i++;
		}
		return r;
	}
	
	static void copy(int[] t, int[] u) {
		System.arraycopy(t, 0, u, 0, 16);
	}
	
	static boolean dead(int[] t) {
		boolean r;
		if (deadisCASE1(t))
			r = deadCASE1(t);
		else
			r = deadCASE2(t);
		return r;
	}
	
	static boolean deadisCASE1(int[] t) {
		int i = 1;
		boolean ok = true;
		while (i != 5 && ok) {
			ok = t[i] + t[5 + i] == MAX[i];
			i++;
		}
		return ok;
	}
	
	static boolean deadCASE1(int[] t) {
		return t[t[12]] > t[5 + t[12]];
	}
	
	static boolean deadCASE2(int[] t) {
		return t[10] == 1;
	}
	
	static boolean isLegal(int[] t, int x, int y) {
		if (!(0 <= x && x <= y && y <= 4))
			return false;
		if (t[t[10] * 5 + t[11 + x]] == 0)
			return false;
		if (t[5 + t[11 + y]] + t[t[11 + y]] == MAX[t[11 + y]])
			return false;
		return true;
	}
}